import random
from tkinter import *

class Application(Frame):

    def __init__(self, master=None):
        Frame.__init__(self,master)
        self.g=Game()
        self.pack()
        self.createWidgets()
        self.master.bind("<KeyPress>",self.key)

    def key(self, event):
        # print("pressed", repr(event.keysym))
        if (event.keysym == "Left"):
            self.left()
        if (event.keysym == "Right"):
            self.right()
        if (event.keysym == "Up"):
            self.up()
        if (event.keysym == "Down"):
            self.down()

    def createWidgets(self):
        self.g.start()
        self.content=StringVar()
        self.refresh()
        self.label=Label(self, textvariable=self.content)
        self.label.pack()
        # self.leftbutton = Button(self,text='<',command=self.left)
        # self.leftbutton.pack()
        # self.rightbutton = Button(self,text='>',command=self.right)
        # self.rightbutton.pack()
        # self.topbutton = Button(self,text='^',command=self.up)
        # self.topbutton.pack()
        # self.downbutton = Button(self,text='v',command=self.down)
        # self.downbutton.pack()

        # < Left > 左箭头
        # < Up > 上箭头
        # < Right > 右箭头
        # < Down >

    def left(self):
        self.operation(1)

    def right(self):
        self.operation(2)

    def up(self):
        self.operation(3)

    def down(self):
        self.operation(4)

    def operation(self,direct):
        if(self.g.move(direct)==-1):
            return
        self.g.addData()
        if(self.g.checkWin()==1):
            self.refresh()
        else:
            self.endGame()

    def refresh(self):
        self.content.set(self.g.showData(self.g.data)+"\n\n")

    def endGame(self):
        self.content.set(self.g.showData(self.g.data)+"\n\nfinish")

class Game:
    def __init__(self,xnum=4,ynum=4):
        self.x=xnum
        self.y=ynum

    def start(self):
        self.initGame()

    def initGame(self):
        self.score=0
        self.rand=[2,4]
        self.data=[[0 for i in range(0,self.y)] for i in range(0,self.x)]
        self.addData()

    def trans(self, data):
        newData=[[0 for i in range(0,self.x)] for i in range(0,self.y)]
        for i in range(0,self.x):
            for j in range(0,self.y):
                newData[j][i]=data[i][j]
        return newData.copy()

    def addData(self):
        self.getBlank()
        self.random()

    def checkWin(self):
        return 1

    def getBlank(self):
        self.blank = []
        for i in range(0, self.x):
            for j in range(0, self.y):
                if (self.data[i][j] == 0):
                    self.blank.append([i, j])

    def random(self):
        if(len(self.blank)>0):
            index=random.choice(self.blank)
            num = random.choice(self.rand)
            self.data[index[0]][index[1]]=num


    def showData(self,data):
        text=""
        for i in range(0,len(data)):
            for j in range(0,len(data[i])):
                text+=str(data[i][j])
                if(j<len(data[i])-1):
                    text+="\t"
            text+="\n\n\n"
        return text

    def left(self):
        self.move(1)

    def right(self):
        self.move(-1)

    def move(self,direct):
        #direct 1 left 2 right

        newData=self.data.copy()

        if(direct==2):
            for i in range(0,len(newData)):
                newData[i].reverse()
        if(direct==3):
            newData=self.trans(newData)
        if(direct==4):
            newData=self.trans(newData)
            for i in range(0,len(newData)):
                newData[i].reverse()
        movedData = self.moveLeft(newData)

        if (direct == 2):
            for i in range(0,len(newData)):
                movedData[i].reverse()
        if (direct == 3):
            movedData = self.trans(movedData)
        if (direct == 4):
            for i in range(0,len(newData)):
                movedData[i].reverse()
            movedData = self.trans(movedData)

        if(movedData==self.data):
            return -1
        else:
            self.data=movedData
        return 1

    def moveLeft(self,data):
        newData = data.copy()
        for i in range(0,self.x):
            newData[i] = self.moveRowLeft(data[i])
        return newData.copy()

    def moveRowLeft(self, row):
        newRow=[]
        for i in range(0, len(row)):
            if (row[i] == 0):
                continue
            else:
                newRow.append(row[i])
        newRow=self.calc(newRow)
        if (len(newRow) < len(row)):
            for i in range(0, len(row) - len(newRow)):
                newRow.append(0)
        return newRow.copy()

    def calc(self,row):
        newRow=[]
        add=0
        for i in range(0,len(row)):
            if(add==1):
                add=0
                continue
            a = row[i]
            if(i<len(row)-1):
                b = row[i+1]
                if(a==b):
                    newRow.append(a+b)
                    add=1
                    continue
            newRow.append(a)
        return newRow.copy()

# g=Game(4,4)
# g.start()
# g.move(4)

a=Application()
a.mainloop()
